﻿<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">

<head>
	<title xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory">附录 J. NEsper .NET 特定信息</title>
	<link rel="stylesheet" href="css/espertech.css" type="text/css">
	<meta xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" name="generator" content="DocBook XSL-NS Stylesheets V1.74.0">
	<meta xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" http-equiv="Content-Type" content="text/html; charset=UTF-8">
	<link rel="home" href="index.html" title="Esper参考文档">
	<link rel="up" href="index.html" title="Esper参考文档">
	<link rel="prev" href="appendix_eventrepxml.html" title="附录 I. 事件表示: org.w3c.dom.Node XML事件">
	<link rel="next" href="ix01.html" title="索引">
</head>

<body>
	<p xmlns:d="http://docbook.org/ns/docbook" id="title"><a href="./index.html" class="site_href"><strong>www.espertech.com</strong></a><a href="http://www.espertech.com/esper/esper-documentation/" class="doc_href"><strong>文档</strong></a></p>
	<ul xmlns:d="http://docbook.org/ns/docbook" class="docnav">
		<li class="previous"><a accesskey="p" href="appendix_eventrepxml.html"><strong>上一页</strong></a></li>
		<li class="next"><a accesskey="n" href="ix01.html"><strong>下一页</strong></a></li>
	</ul>
	<div class="appendix" lang="en-US">
		<div class="titlepage">
			<div>
				<div>
					<h2 class="title"><a id="appendix_dotnet"></a>附录 J. NEsper .NET 特定信息</h2>
				</div>
			</div>
		</div>
		<p>
			本节为NEsper .NET用户提供相关信息。
		</p>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_general"></a>J.1. .NET通用信息</h2>
					</div>
				</div>
			</div>
			<p>
				<code class="literal">System.Collections.IEnumerable</code>和<code class="literal">System.Collections.Generic.IEnumerable&lt;T&gt;</code>在大多数需要集合的地方都被支持。
			</p>
			<p>
				关于<code class="literal">DateTime</code>差异，CLR日期时间的基准是<code class="literal">1/1/0001 12:00:00AM</code>。日期时间被转换为ticks然后再转换为毫秒。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_annotation"></a>J.2. .NET与注解</h2>
					</div>
				</div>
			</div>
			<p>
				注解通过.NET属性实现。注解必须派生自<code class="literal">System.Attribute</code>并且必须使用.NET属性命名约定，例如<code class="literal">@Hint</code>实现为<code class="literal">HintAttribute</code>。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_locksconcurrency"></a>J.3. .NET与锁和并发</h2>
					</div>
				</div>
			</div>
			<p>
				NEsper提供了一个可配置的锁管理器，每个AppDomain配置一次：<code class="literal">com.espertech.esper.compat.threading.LockManager</code>用于锁的提供。
			</p>
			<div class="itemizedlist">
				<ul compact="compact">
					<li>
						<p>
							标准系统锁是默认选项。
						</p>
					</li>
					<li>
						<p>
							可以使用自旋锁和轻量锁。
						</p>
					</li>
					<li>
						<p>
							可以利用自定义锁实现。
						</p>
					</li>
				</ul>
			</div>
			<p>
				开箱即用的锁实现包括：
			</p>
			<div class="itemizedlist">
				<ul compact="compact">
					<li>
						<p>
							MonitorLock - 使用CLR提供的对象锁定机制，等同于Java的wait()和notify()
						</p>
					</li>
					<li>
						<p>
							MonitorSpinLock - 使用CLR提供的System.Threading.SpinLock
						</p>
					</li>
					<li>
						<p>
							MonitorSlimLock - 为NEsper构建的自旋锁早期模型
						</p>
					</li>
				</ul>
			</div>
			<p>
				<code class="literal">com.espertech.esper.compat.threading.ReaderWriterLockManager</code>用于读写锁管理。
			</p>
			<div class="itemizedlist">
				<ul compact="compact">
					<li>
						<p>
							标准读写锁是默认选项。
						</p>
					</li>
					<li>
						<p>
							提供了轻量读写锁。
						</p>
					</li>
					<li>
						<p>
							提供了公平和FIFO读写锁实现，但不受官方支持。
						</p>
					</li>
				</ul>
			</div>
			<p>
				读写锁是单独的结构，开箱即用的实现包括：
			</p>
			<div class="itemizedlist">
				<ul compact="compact">
					<li>
						<p>
							StandardReaderWriterLock - 使用CLR提供的System.Threading.ReaderWriterLock()
						</p>
					</li>
					<li>
						<p>
							SlimReaderWriterLock - 使用CLR提供的System.Threading.ReaderWriterLockSlim()
						</p>
					</li>
					<li>
						<p>
							FifoReaderWriterLock - 构建用于镜像某些Java读写锁语义 - 通常不推荐且不受NEsper官方支持
						</p>
					</li>
					<li>
						<p>
							FairReaderWriterLock - 构建用于镜像某些Java读写锁语义 - 通常不推荐且不受NEsper官方支持
						</p>
					</li>
				</ul>
			</div>
			<p>
				在NEsper中，初始化时提供或创建一个容器。
			</p>
			<pre xmlns="" xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" class="">DefaultReaderWriterLockManager rwLockManager = (DefaultReaderWriterLockManager) container.RWLockManager();</pre>
			<p>
				应用程序获取锁管理器后，可以设置其DefaultLockTimeout属性。
			</p>
			<pre xmlns="" xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" class="">rwLockManager.DefaultLockTimeout = 1000000L;</pre>
			<p>
				锁管理器依赖于一个工厂。可以通过设置DefaultLockFactory属性来覆盖默认工厂。
			</p>
			<pre xmlns="" xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" class="">rwLockManager.DefaultLockFactory = (lockTImeout) =&gt; ...();</pre>
			<p>
				如果应用程序希望通过类型控制，可以为特定类型注册锁工厂。
			</p>
			<pre xmlns="" xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" class="">rwLockManager.RegisterLockFactory(typeof(foo), (lockTimeout) =&gt; myCustomerLock());</pre>
			<p>
				没有针对特定类型的锁超时设置。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_threading"></a>J.4. .NET与线程</h2>
					</div>
				</div>
			</div>
			<p>
				<code class="literal">com.espertech.esper.compat.threading.ThreadLocalManager</code>用于线程本地管理。
			</p>
			<div class="itemizedlist">
				<ul compact="compact">
					<li>
						<p>
							快速线程本地实现是默认选项 - 非.NET标准。
						</p>
					</li>
					<li>
						<p>
							标准实现可用 - 但发现速度明显较慢。
						</p>
					</li>
				</ul>
			</div>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_timer"></a>J.5. .NET与计时器</h2>
					</div>
				</div>
			</div>
			<p>
				本节仅适用于内部系统时间计时器，不适用于外部计时器(当应用程序提供时间时)。
			</p>
			<p>
				由于通常在Windows上运行，NEsper默认依赖高性能多媒体计时器。该计时器设计用于同步到显示速率，因此可以以1ms或更好的精度运行。高精度计时器在AppDomain释放时被清理。
			</p>
			<p>
				但是，如果应用程序是netcoreapp，并且由于netcoreapp设计为跨平台运行，人们会希望依赖.NET提供的标准计时器。
				要使用替代计时器，必须配置容器(如下所示)。这将告诉容器创建一个<code class="literal">SimpleTimerFactory</code>。保留默认行为，但现在可以更改行为以使用CPU消耗较少的计时器。
			</p>
			<pre xmlns="" xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" class="">var container = ContainerExtensions.CreateDefaultContainer(false);

container.Register&lt;ITimerFactory&gt;(
	ic =&gt; new SimpleTimerFactory(),
	Lifespan.Singleton);

container
	.InitializeDefaultServices()
	.InitializeDatabaseDrivers();

var config = new Configuration(container);
var esperRuntime = EPRuntimeProvider.GetRuntime("URI Here", config);</pre>
			<p>
				上述代码创建一个容器，注册应用程序可能需要的服务，然后为任何剩余的服务和数据库驱动程序初始化默认值。
				<code class="literal">InitializeDefaultServices()</code>初始化容器中的默认服务(如果尚未提供)。因此，如果要提供任何类型的服务，必须在调用<code class="literal">InitializeDefaultServices()</code>之前将其添加到容器中。
				否则，将安装默认服务，并且如果尝试替换已注册的服务，将主动抛出异常。<code class="literal">CreateDefaultContainer(false)</code>仅实例化一个新的Container对象。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_configuration"></a>J.6. .NET NEsper配置</h2>
					</div>
				</div>
			</div>
			<p>
				提供<code class="literal">com.espertech.esper.util.EsperSectionHandler</code>从标准.NET配置中读取Esper配置。必须作为<code class="literal">configSection</code>添加才能使用。
			</p>
			<p>
				对于Esper配置未处理的项，使用<code class="literal">com.espertech.esper.compat.CompatSettings</code>。
				这些通常应用于整个AppDomain，意味着它们对容器实际上是静态的。
				这些涵盖以下项目：
			</p>
			<div class="itemizedlist">
				<ul compact="compact">
					<li>
						<p>
							<code class="literal">DefaultLockType</code>。
						</p>
					</li>
					<li>
						<p>
							<code class="literal">DefaultReaderWriterLockType</code>。
						</p>
					</li>
					<li>
						<p>
							<code class="literal">MonitorLockTimeout</code>。
						</p>
					</li>
					<li>
						<p>
							<code class="literal">ReaderLockTimeout</code>。
						</p>
					</li>
					<li>
						<p>
							<code class="literal">WriterLockTimeout</code>。
						</p>
					</li>
					<li>
						<p>
							<code class="literal">DefaultThreadLocalType</code>。
						</p>
					</li>
				</ul>
			</div>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_eventrep_intro"></a>J.7. .NET事件底层对象</h2>
					</div>
				</div>
			</div>
			<div class="table"><a id="d0e64636"></a>
				<p class="title"><b>表 J.1. 事件底层.NET对象</b></p>
				<div class="table-contents">
					<table summary="事件底层.NET对象" border="1">
						<colgroup>
							<col>
							<col>
						</colgroup>
						<thead>
							<tr>
								<th>Java类</th>
								<th>描述</th>
							</tr>
						</thead>
						<tbody>
							<tr>
								<td><code class="literal">System.Object</code></td>
								<td>任何具有属性的.NET对象。</td>
							</tr>
							<tr>
								<td><code class="literal">System.Collections.Generic.IDictionary</code></td>
								<td>映射事件是<code class="literal">IDictionary</code>接口的实现，其中每个映射条目都是一个属性值。</td>
							</tr>
							<tr>
								<td><code class="literal">System.Array, System.Object[] (对象数组)</code></td>
								<td>对象数组事件是对象数组(类型为<code class="literal">Object[]</code>)，其中每个数组元素都是一个属性值。</td>
							</tr>
							<tr>
								<td><code class="literal">System.Xml.XmlNode</code>和<code class="literal">System.Xml.Linq.XNode</code></td>
								<td>XML文档对象模型(DOM)。</td>
							</tr>
							<tr>
								<td>应用程序类</td>
								<td>通过扩展API提供的插件事件表示。</td>
							</tr>
						</tbody>
					</table>
				</div>
			</div><br class="table-break">
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_eventrep_javabean"></a>J.8. .NET对象事件</h2>
					</div>
				</div>
			</div>
			<p>
				事件类通过自动实现的属性或读写属性提供访问器(getter方法)和修改器(setter方法)。
			</p>
			<p>
				以下是使用自动实现属性的示例：
			</p>
			<pre xmlns="" xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" class="">class NewEmployeeEvent {
  public string FirstName { get; set; }
  public Address Address { get; set; }	
}</pre>
			<p>
				以下是使用读写属性的示例：
			</p>
			<pre xmlns="" xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" class="">class NewEmployeeEvent {
  private string firstName = "N/A";
  private Address address = 0;

  public string FirstName
  {
    get
    {
      return firstName;
    }
    set
    {
      firstName = value;
    }
  }

  public Address Address
  {
    get
    {
      return address;
    }
    set
    {
      address = value;
    }
  }
}</pre>
			<p>
				大小写转换遵循.NET属性约定，采用大写形式。
			</p>
			<p>
				映射索引通过索引运算符处理。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_eventrep_map"></a>J.9. .NET IDictionary事件</h2>
					</div>
				</div>
			</div>
			<p>
				对于.NET，事件可以由实现<code class="literal">IDictionary</code>接口的对象表示。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_eventrep_xml"></a>J.10. .NET XML事件</h2>
					</div>
				</div>
			</div>
			<p>
				XML事件由<code class="literal">System.Xml</code>和<code class="literal">System.Xml.Linq</code>表示。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_eventrep_insertinto"></a>J.11. .NET由<code class="literal">Insert Into</code>实例化和填充的事件对象</h2>
					</div>
				</div>
			</div>
			<p>
				对象需要遵循.NET属性约定。对象可以遵循修改后的约定，使用Get和Set分别实现Java风格的访问器和修改器。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_processingmodel_intro"></a>J.12. .NET基本概念</h2>
					</div>
				</div>
			</div>
			<p>
				Esper和NEsper在基本概念方面没有差异。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_epl_syntax_datatype"></a>J.13. .NET EPL语法 - 数据类型</h2>
					</div>
				</div>
			</div>
			<p>
				数据类型包括<code class="literal">sbyte</code>、<code class="literal">byte</code>、<code class="literal">short</code>、<code class="literal">ushort</code>、<code class="literal">int</code>、<code class="literal">uint</code>、<code class="literal">long</code>、<code class="literal">ulong</code>、<code class="literal">float</code>、<code class="literal">double</code>、<code class="literal">decimal</code>。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_histdata_overview"></a>J.14. .NET通过SQL访问关系数据</h2>
					</div>
				</div>
			</div>
			<p>
				.NET使用基于ADO的驱动程序来完成相同的工作。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_api_receive_results"></a>J.15. .NET API - 接收语句结果</h2>
					</div>
				</div>
			</div>
			<p>
				NEsper在<code class="literal">EPStatement</code>对象上公开事件<code class="literal">events</code>。
			</p>
			<p>
				<code class="literal">UpdateListener</code>在.NET中被<code class="literal">UpdateEventHandler</code>取代。订阅者对象必须实现<code class="literal">Update</code>方法
				或者订阅者对象必须是具有适当数量参数的委托。
			</p>
			<p>
				<code class="literal">setSubscriber</code>方法被<code class="literal">Subscriber</code>属性取代。此属性可以接受对象或委托。
			</p>
			<p>
				<code class="literal">Iterator</code>被<code class="literal">GetEnumerator</code>取代。<code class="literal">SafeIterator</code>被<code class="literal">GetSafeEnumerator</code>取代。
			</p>
			<p>
				在NEsper中，可以使用lambda将委托分配给订阅者：
			</p>
			<pre xmlns="" xmlns:d="http://docbook.org/ns/docbook" xmlns:rf="java:org.jboss.highlight.XhtmlRendererFactory" class="">statement.Subscriber = new Action&lt;TradeReportEvent, NesperTest&gt;((a, b) =&gt; {
  Debug.Print("got here");
});</pre>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_api_admin_listeners"></a>J.16. .NET API - 添加监听器</h2>
					</div>
				</div>
			</div>
			<p>
				监听器被<code class="literal">UpdateEventHandlers</code>取代，例如<code class="literal">countStatement.Events += (sender, args) =&gt; { DoWork(); }</code>。
			</p>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_config_database_ref"></a>J.17. .NET配置 - 关系数据库访问</h2>
					</div>
				</div>
			</div>
			<p>
				通过选择<code class="literal">DbDriver</code>获取连接，这是NEsper的构造。
			</p>
			<div class="itemizedlist">
				<ul compact="compact">
					<li>
						<p>
							<code class="literal">DbDriverGeneric</code>：基于位置或名称的驱动程序，必须在使用前完全配置。
						</p>
					</li>
					<li>
						<p>
							<code class="literal">DbDriverMySQL</code>：基于位置的驱动程序，使用'?'前缀。
						</p>
					</li>
					<li>
						<p>
							<code class="literal">DbDriverODBC</code>：基于位置的驱动程序，使用'?'前缀。
						</p>
					</li>
					<li>
						<p>
							<code class="literal">DbDriverSqlServer</code>：将基于位置的参数转换为带有'@'前缀的基于名称的SqlParameters。
						</p>
					</li>
				</ul>
			</div>
		</div>
		<div class="sect1" lang="en-US">
			<div class="titlepage">
				<div>
					<div>
						<h2 class="title"><a id="appendix_dotnet_configuration_logging"></a>J.18. .NET配置 - 日志配置</h2>
					</div>
				</div>
			</div>
			<p>
				Log4j被.NET Commons Logging取代。
			</p>
		</div>
	</div>
	<ul xmlns:d="http://docbook.org/ns/docbook" class="docnav">
		<li class="previous"><a accesskey="p" href="appendix_eventrepxml.html"><strong>上一页</strong>附录 I. 事件表示: org.w3c.dom.Nod...</a></li>
		<li class="up"><a accesskey="u" href="#"><strong>页首</strong></a></li>
		<li class="home"><a accesskey="h" href="index.html"><strong>首页</strong></a></li>
		<li class="next"><a accesskey="n" href="ix01.html"><strong>下一页</strong>索引</a></li>
	</ul>
</body>

</html>